package com.xjm.service.serviceImpl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.xjm.constant.Update;
import com.xjm.entity.model.CartItemsModel;
import com.xjm.entity.model.OrderItemsModel;
import com.xjm.entity.model.OrdersModel;
import com.xjm.entity.model.TrackingModel;
import com.xjm.excption.AppException;
import com.xjm.mapper.OrdersMapper;
import com.xjm.service.ICartItemsService;
import com.xjm.service.IOrderItemsService;
import com.xjm.service.IOrdersService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.xjm.service.ITrackingService;
import com.xjm.utils.SpaceApiUtil;
import com.xjm.utils.UserContext;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author xjm
 * @since 2025-03-03
 */
@Service
@RequiredArgsConstructor
public class OrdersServiceImpl extends ServiceImpl<OrdersMapper, OrdersModel> implements IOrdersService {

    private final IOrderItemsService orderItemsService;
    private final OrdersMapper ordersMapper;
    private final ICartItemsService cartItemsService;
    private final ITrackingService trackingService;

    @Override
    @Transactional
    public void createOrderWithItems(OrdersModel data) {
        Integer userId = UserContext.getUserId();
        OrdersModel ordersModel = new OrdersModel();
        ordersModel.setUserId(userId);
        ordersModel.setAddressId(data.getAddressId());
        ordersModel.setTotalAmount(data.getTotalAmount());
        ordersModel.setOrderNo(data.getOrderNo());
        ordersModel.setStatus(data.getStatus());
        ordersMapper.insert(ordersModel);
        data.getOrderItems().forEach(item -> {
            item.setOrderId(ordersModel.getId());
        });
        orderItemsService.saveBatch(data.getOrderItems());
        // 删除购物车对应商品
        List<Integer> proIds = data.getOrderItems().stream().map(OrderItemsModel::getProductId).toList();
        LambdaQueryWrapper<CartItemsModel> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(CartItemsModel::getUserId, userId);
        queryWrapper.in(CartItemsModel::getProductId, proIds);
        cartItemsService.remove(queryWrapper);
    }


    @Override
    public void cancel(String id) {
        LambdaQueryWrapper<OrdersModel> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(OrdersModel::getId, id);
        wrapper.eq(OrdersModel::getStatus, "pending");
        OrdersModel ordersModel = ordersMapper.selectOne(wrapper);
        if (ordersModel == null) {
            throw new AppException("订单不存在或状态不正确");
        }
        ordersModel.setStatus("cancelled");
        ordersMapper.updateById(ordersModel);
    }

    @Override
    public void pay(String id) {
        LambdaQueryWrapper<OrdersModel> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(OrdersModel::getId, id);
        wrapper.eq(OrdersModel::getStatus, "pending");
        OrdersModel ordersModel = ordersMapper.selectOne(wrapper);
        if (ordersModel == null) {
            throw new AppException("订单不存在或状态不正确");
        }
        ordersModel.setStatus("processing");
        ordersMapper.updateById(ordersModel);
    }

    @Transactional
    @Override
    public void send(Integer id, String logisticsNo) {
        LambdaQueryWrapper<OrdersModel> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(OrdersModel::getId, id);
        wrapper.eq(OrdersModel::getStatus, "processing");
        OrdersModel ordersModel = ordersMapper.selectOne(wrapper);
        if (ordersModel == null) {
            throw new AppException("订单不存在或状态不正确");
        }
        TrackingModel trackingModel = new TrackingModel();
        String orderType = SpaceApiUtil.getOrderType(logisticsNo);
        trackingModel.setCpCode(orderType);
        trackingModel.setOrderId(id);
        trackingModel.setTraceNo(logisticsNo);
        trackingService.save(trackingModel);
        ordersModel.setStatus("shipped");
        ordersMapper.updateById(ordersModel);
    }
}
